﻿using Cofe.Core.Filter;
using Cofe.Core.Property;
using Cofe.Core.Utils;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Reactive.Linq;
using System.Diagnostics;
using Cofe.Core.Interfaces;
using System.ComponentModel.Composition;

namespace Cofe.Core.Entry
{
    public abstract class EntryListPropertyProvider : PropertyProviderBase
    {

        #region Constructor

        [Export(typeof(ICofeService))]
        [ServicePriority(ServicePriorityAttribute.DefaultPriority_COFE)]
        public class Regenerator : IEntryPrimaryPPRegenerator
        {
            public Task<IPropertyProvider> RegenerateAsync(IPropertyCache propertyCache)
            {
                IPropertyProvider retVal = null;
                var ELtype = EnumUtils.GetEntryListType(propertyCache.GetOneProperty<string>(CofeProperties.Type));
                switch (ELtype)
                {
                    case EntryListTypes.CustomEntryList:
                        string fullName = propertyCache.GetOneProperty<string>(CofeProperties.FullParseName);
                        bool isRoot = fullName.StartsWith("{");
                        string label = fullName.TrimStart('{').TrimEnd('}');
                        var ph = CofeServices.EntryListRegistrar.Find(fullName);
                        
                        if (ph == null)
                            retVal = null;
                        else retVal = new CustomEntryListPrimaryPP(label, isRoot);
                        break;
                    case EntryListTypes.AutoEntryList:
                        string filterStr = propertyCache.GetOneProperty<string>(CofeEntryListProperties.FilterString);
                        retVal = new AutoEntryListPropertyProvider(filterStr);
                        break;

                }
                return Task<IPropertyProvider>.FromResult(retVal);
            }
        }


        public EntryListPropertyProvider(EntryListTypes entryListType, string name)
            : base(PropertyDefinitions.CofeDefinitions, PropertyDefinitions.CofeDirDefinitions,
            PropertyDefinitions.CofeEntryListDefinitions)
        {
            _name = PathFE.SantizeFileName(name);
            _entryListType = entryListType;

            //registerProperties(CofeProperties.FullParseName, () => _filterStr);

            registerProperties(CofeProperties.Type, () => EnumUtils.GetPropertyName(entryListType));

            registerProperties(CofeProperties.ParentPropertyProvider, () => _parentPP,
                (pp) => { if (_parentPP == null) { _parentPP = pp.ValueAs<IPropertyProvider>(); return true; } return false; });

            registerProperties(CofeProperties.Parent, () => null, (pp) => { Debugger.Break(); return false; });

            registerProperties(CofeProperties.FullParseName, () => getParseName());
            registerProperties(CofeProperties.Name, () => PathFE.GetFileName(getParseName()));
            registerProperties(CofeEntryListProperties.EntryListType, () => _entryListType);
            registerProperties(CofeEntryListProperties.IsAttached, () => _isAttached, (v) => { _isAttached = v.ValueAsBoolean; return true; });
        }

        #endregion

        #region Methods

        protected virtual string getParseName()
        {
            string name = _name ?? "Unnamed";
            if (_parentPP != null)
            {
                var parseName = _parentPP.GetOneProperty<string>(CofeProperties.FullParseName);
                return PathFE.Combine(parseName, name);
            }
            else return name;
        }

        protected virtual CofeAttributes getBaseCofeAttributes()
        {
            //if (_parent != null)
            //    return 
            //        _parent.CofeAttributes.HasFlag(CofeAttributes.NotCachable) ?
            //        (CofeAttributes.Browsable | CofeAttributes.NotCachable) : CofeAttributes.Browsable;
            //else
            return CofeAttributes.Browsable;
        }

        #endregion

        #region Data

        private EntryListTypes _entryListType;
        private IPropertyProvider _parentPP = null;
        protected string _name = null;
        private bool _isAttached = false;
        private List<object> _supportedProperties = new List<object>();

        #endregion

        #region Public Properties



        #endregion



    }
}
